<?php

namespace App\Task;

use App\Model\DataAdEcpmBackhaul;
use App\Model\DataBackhaulSetting;
use App\Model\DataPaymentBackhaul;
use App\Model\DataSpread;
use App\Model\DataAdEcpm;
use App\Model\Payment;
use GuzzleHttp\Client;
use Hyperf\Crontab\Annotation\Crontab;
use Hyperf\DbConnection\Db;
use Hyperf\Logger\LoggerFactory;
use Hyperf\Utils\ApplicationContext;
use Psr\Log\LoggerInterface;



class BackhaulDyEcpmByImpressionTask
{
    protected LoggerInterface $logger;

//    public static $token = '7FE11418980F94B82110648EC0DAFD2B';

    public static $test_user = ['345','372','436'];

    public static $reportUrl = "https://analytics.oceanengine.com/api/v2/conversion";

//    public static $starReportUrl = "https://ad.oceanengine.com/track/activate/";
    public function __construct(protected LoggerFactory $loggerFactory)
    {
        $this->logger = $this->loggerFactory->get('log', 'BackhaulDyEcpmByImpression');
    }

    public function execute()
    {
        $container = ApplicationContext::getContainer();
        $redis = $container->get(\Hyperf\Redis\RedisFactory::class)->get('default');

        $this->logger->info(date('Y-m-d H:i:s') . '------------------------定时获取redis上的数据');
        $this->logger->info('开始获取用户未处理的数据');
        $today_date = date('Y-m-d 0:0:0',time());
        $nowTime = date('Y-m-d H:i:s',time());
        $time = date('Y-m-d H:i:s',time()-7200);
//        return;
        $handleKey = 'dy_backhaul_Impression_ecpm_live';
        try {

            $keyData = $redis->get($handleKey);
            if(!empty($keyData)){

                $this->logger->info('存在处理中的订单进程');
                $this->logger->info(date('Y-m-d H:i:s') . '------------------------结束定时获取订单进行上报');
                return;
            }else{
                $redis->set($handleKey,1);
            }
            Db::beginTransaction();
            //获取需要处理的订单
            $adEcpmData = DataAdEcpm::query()->where(['is_handle' => 'N','applet_id' => '20004'])->get();


            if($adEcpmData->isNotEmpty()) {
                //判断是否
                $this->logger->info('订单的数据为数量为：', [count($adEcpmData)]);
                $errorMeg = [];
                foreach ($adEcpmData as $adEcpmDatum) {
                    //查找这个用户的userInfo

                    $userInfo = Db::table('data_user_' . $adEcpmDatum->applet_id)->where(['id' => $adEcpmDatum->user_id])->first();
                    $this->logger->info('获取订单的用户user,id为:', [$userInfo->id]);
                    if (!empty($userInfo)) {

                        $this->logger->info('获取订单对应的推广链接,最新的推广链ID:', [$adEcpmDatum->spread_id]);
                        $spreadInfo = DataSpread::query()->where(['id' => $adEcpmDatum->spread_id])->first();

                        if (!empty($spreadInfo)) {

                            $backhaulsettingInfo = DataBackhaulSetting::query()->where(['id' => $spreadInfo->backhaul_setting_id])->first();
                            if (!empty($backhaulsettingInfo)) {

                                if(!empty($userInfo->click_id) && $userInfo->click_id != 'undefined') {
                                    //先获取订单的推广链接ID
                                    $this->logger->info('获取订单所对应的推广最新的回传token', [$userInfo->id]);
                                    $this->handOrder($redis, $adEcpmDatum, $userInfo, $spreadInfo,$backhaulsettingInfo);
                                }

                            }else{
                                $adEcpmDatum->is_handle = 'Y';
                                $adEcpmDatum->save();
                                $this->logger->error('推广链接不存在对应的回传配置', [$adEcpmDatum->id]);
                                $errorMeg[] = [
                                    'ad_ecpm_id' => $adEcpmDatum->id,
                                    'created_at' => date('Y-m-d H:i:s', time()),
                                    'errorMsg' => '推广链接不存在对应的回传配置'
                                ];

                            }
                        } else {
                            $adEcpmDatum->is_handle = 'Y';
                            $adEcpmDatum->save();
                            $this->logger->error('订单不存在推广链接ID', [$adEcpmDatum->id]);
                            $errorMeg[] = [
                                'ad_ecpm_id' => $adEcpmDatum->id,
                                'created_at' => date('Y-m-d H:i:s',time()),
                                'errorMsg' => '订单不存在推广链接ID'
                            ];
                        }
                    } else {
                        $adEcpmDatum->is_handle = 'Y';
                        $adEcpmDatum->save();
                        $this->logger->error('订单不存在用户', [$adEcpmDatum->id]);
                        $errorMeg[] = [
                            'ad_ecpm_id' => $adEcpmDatum->id,
                            'errorMsg' => '订单不存在用户',
                            'created_at' => date('Y-m-d H:i:s',time())
                        ];
                    }
                }
                if(!empty($errorMeg)){
                    Db::table('data_ad_ecpm_backhaul_error')->insert($errorMeg);
                }
            }else{
                $this->logger->info('没有Ecpm订单需要上报');
            }

            $redis->del($handleKey);
            Db::commit();
        }catch (\Exception $e){
            $redis->del($handleKey);
            $this->logger->error('请求回传|错误：' . $e->getLine() . '|' . $e->getMessage());
            Db::rollBack();
        }
        $this->logger->info(date('Y-m-d H:i:s') . '------------------------结束定时获取订单进行上报');
    }

    public function handOrder($redis,$adEcpmDatum,$userInfo,$spreadInfo,$backhaulsettingInfo){

        $start_date = date('Y-m-d 00:00:00',time());
        $end_date = date('Y-m-d 23:59:59',time());
        //判断回传配置中是否需要回传
        $this->logger->info('判断回传配置中是否需要回传',[$backhaulsettingInfo->is_impression]);
        if($backhaulsettingInfo->is_impression == 'Y'){
            //判断用户的染色时间是否为今天
            $this->logger->info('判断用户的染色时间是否为今天',[$userInfo->dyeing_time]);
            if($start_date <= $userInfo->dyeing_time && $end_date >= $userInfo->dyeing_time) {
                $uploadData = $this->uploadPayment($userInfo);
                if ($uploadData) {
                    $this->logger->info('上报回传成功:', [$adEcpmDatum->id]);
                    $this->installRel($userInfo,$adEcpmDatum,$backhaulsettingInfo);
                    $adEcpmDatum->is_handle = 'Y';
                    $adEcpmDatum->save();
                }
            }else{
                $this->logger->info('用户的染色时间已过期',[$userInfo->dyeing_time]);
                $errorMeg =[
                    'ad_ecpm_id' => $adEcpmDatum->id,
                    'errorMsg' => '用户的染色时间已过期 用户染色时间为：'.$userInfo->dyeing_time,
                    'created_at' => date('Y-m-d H:i:s',time())
                ];

                Db::table('data_ad_ecpm_backhaul_error')->insert($errorMeg);
                $adEcpmDatum->is_handle = 'Y';
                $adEcpmDatum->save();
            }
        }
    }

    public function installRel($userInfo,$adEcpmInfo,$backhaulsettingInfo,$type=1,$redis_key=''){


        $open_id = $userInfo->xc_open_id ?? '';
        $ad_id = $userInfo->ad_id ?? '';
        $clue_token = $userInfo->clue_token  ?? '';
        $click_id =$userInfo->click_id ?? '';

        DataAdEcpmBackhaul::create([
            'user_id' => $userInfo->id,
            'applet_id' => $adEcpmInfo->applet_id,
            'ad_ecpm_id' => $adEcpmInfo->id,
            'xc_open_id' => $open_id,
            'clue_token' => $clue_token,
            'click_id' => $click_id,
            'ad_id' => $ad_id,
            'type' => $type,
            'backhaul_setting_id' => $backhaulsettingInfo->id,
            'reids_key' => $redis_key,
            'spread_id' => $adEcpmInfo->spread_id
        ]);
    }
    public function uploadPayment($userInfo){


        $click_id =$userInfo->click_id;
        try {

            $params = [
                "context" =>
                    ["ad" =>[
                        'callback' => $click_id
                    ],
                    ],
                "event_type"  => "impression",
//                "props" => [
//                    'pay_amount' => $paymentInfo->amount
//                ],
//                "timestamp" => time()*1000
            ];

            $linkUrl = self::$reportUrl;
            $this->logger->info('请求抖音上报Ecpm数据：'.PHP_EOL.var_export(['result' => $params], true));
            $this->logger->info('请求抖音上报EcpmUrl：'.$linkUrl);
            //开始上传
//            $result  = $this->request($params, $linkUrl,'POST');
            $result['code'] = 0;
            if($result['code'] == 0 ){
                $this->logger->info('调用抖音上报Ecpm接口成功 返回数据：'.PHP_EOL.var_export(['result' => $result], true));
                //插入订单回传关联表
                return true;
            }else{
                $this->logger->error('调用抖音上报Ecpm接口失败 返回数据：'.PHP_EOL.var_export(['result' => $result], true));
            }

        }catch (\Exception $e){

            $this->logger->error('请求回传|错误：' . $e->getLine() . '|' . $e->getMessage());
            return false;
        }

        return false;
    }
    /**
     * 传入数组进行HTTP POST请求
     */
    function request(array $params, string $url,string $method,string $access_token = null)
    {
        $client   = new Client([
            'timeout' => 3
        ]);
        $headers       = ['Content-Type' => 'application/json'];
        if(!empty($access_token)){
            $headers['access-token'] = $access_token;
        }

        $requestParams = [
            'headers' => $headers,
        ];
        if ($method == 'GET') {
            $requestParams['query'] = $params;
        } else {
            $requestParams['json'] = $params;//json_encode($params,JSON_UNESCAPED_UNICODE);
        }
        $response = $client->request($method,$url, $requestParams);
        if ($response->getStatusCode() !== 200) {
            return '';
        }
        $result   = $response->getBody()->getContents();
        $resultArr = json_decode($result,true);
        return $resultArr;

    }
}